package com.demomaster.quickaccessibility.service;

import android.graphics.Rect;
import android.os.Build;
import android.text.TextUtils;
import android.util.Log;
import android.view.accessibility.AccessibilityNodeInfo;

import com.demomaster.quickaccessibility.utils.DisplayUtil;

import java.util.ArrayDeque;
import java.util.ArrayList;
import java.util.Deque;
import java.util.LinkedHashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Queue;
import java.util.regex.Matcher;
import java.util.regex.Pattern;


public class AccessNodeFinder {
    private static String TAG = AccessNodeFinder.class.getSimpleName();
    static AccessNodeFinder instance;

    public static AccessNodeFinder getInstance() {
        if (instance == null) {
            instance = new AccessNodeFinder();
        }
        return instance;
    }

    public AccessNodeFinder() {
//        accessNodeMap = new LinkedHashMap<>();
//        idMap = new LinkedHashMap<>();
//        textMap = new LinkedHashMap<>();
//        descriptionMap = new LinkedHashMap<>();
    }

    static boolean hasUpdate = true;


    /**
     * 通知有变动需要更新
     */
    public void noteUpdate() {
        hasUpdate = true;
    }

    //private static Map<Integer, AccessibilityNodeInfo> accessNodeMap;

    public static Map<Integer, AccessibilityNodeInfo> getAccessNodeMap8() {
        if (System.currentTimeMillis() - lastUpdateRootNodeTime < 1000) {
            return null;// accessNodeMap;
        }
        AccessibilityNodeInfo rootNode2 = QuickAccessibilityService.instance.getRootInActiveWindow();
        long t1 = System.currentTimeMillis();
        reSetRootNode3(rootNode2);
        hasUpdate = false;//更新已处理
        //Log.d(TAG, "updateRootNode1 耗时：" + (System.currentTimeMillis() - t1) + ",总数=" + accessNodeMap.size());

//        AccessibilityNodeInfo rootNode3 = QuickAccessibilityService.instance.getRootInActiveWindow();
//        long t2 = System.currentTimeMillis();
//        ArrayList<AccessibilityNodeInfo> nodeInfos = new ArrayList<>();
//        getAllChildNode(nodeInfos, rootNode3);
//        Log.d(TAG, "updateRootNode2 耗时：" + (System.currentTimeMillis() - t2) + ",总数=" + nodeInfos.size());
//        long t3 = System.currentTimeMillis();;
//        reSetRootNode3(rootNode2);
//        hasUpdate = false;//更新已处理
//        Log.d(TAG, "updateRootNode3 耗时：" + (System.currentTimeMillis() - t3) + ",总数=" + getAccessNodeMap().size());
//        long t4 = System.currentTimeMillis();
//        List<AccessibilityNodeInfo> nodeInfos4 = getAllChildNode2(rootNode2);
//        Log.d(TAG, "updateRootNode4 耗时：" + (System.currentTimeMillis() - t4) + ",总数=" + nodeInfos4.size());

        return null;// accessNodeMap;
    }

    public static List<AccessibilityNodeInfo> getAccessNodeList() {
        List<AccessibilityNodeInfo> list = new ArrayList<>();
       /* for (Map.Entry entry : getAccessNodeMap().entrySet()) {
            list.add((AccessibilityNodeInfo) entry.getValue());
        }*/

        Deque<AccessibilityNodeInfo> stack = new ArrayDeque<>();
        stack.push(QuickAccessibilityService.instance.getRootInActiveWindow());

        while (!stack.isEmpty()) {
            AccessibilityNodeInfo currentNode = stack.pop();
            // 执行操作...
            list.add(currentNode);
            // 将子节点按逆序压入栈中，保证遍历顺序与递归相同（深度优先）
            for (int i = currentNode.getChildCount() - 1; i >= 0; i--) {
                AccessibilityNodeInfo child = currentNode.getChild(i);
                if (child != null) {
                    stack.push(child);
                }
            }
        }
        return list;
    }
    //    static Map<String, List<Integer>> idMap;
//    static Map<String, List<Integer>> textMap;
//    static Map<String, List<Integer>> descriptionMap;

    public static long lastUpdateRootNodeTime = 0;

    private void updateRootNode() {
        if (System.currentTimeMillis() - lastUpdateRootNodeTime < 3000) {
            return;
        }
        if (hasUpdate) {
//            nodeInfoMap.clear();
//            idMap.clear();
//            textMap.clear();
//            descriptionMap.clear();
//            AccessibilityNodeInfo rootNode = QuickAccessibilityService.instance.getRootInActiveWindow();
//            long t1 = System.currentTimeMillis();
//            reSetRootNode(rootNode);
//            hasUpdate = false;//更新已处理
//            QDLogger.println("updateRootNode 耗时1：" + (System.currentTimeMillis() - t1));

//            idMap.clear();
//            textMap.clear();
//            descriptionMap.clear();
//            AccessibilityNodeInfo rootNode2 = QuickAccessibilityService.instance.getRootInActiveWindow();
//            long t2 = System.currentTimeMillis();
//            reSetRootNode2(rootNode2);
//            hasUpdate = false;//更新已处理
//            Log.d(TAG, "updateRootNode 耗时：" + (System.currentTimeMillis() - t2) + ",总数：" + nodeInfoMap.size());
//
//
//            nodeInfoMap.clear();
            AccessibilityNodeInfo rootNode2 = QuickAccessibilityService.instance.getRootInActiveWindow();
            long t3 = System.currentTimeMillis();
            reSetRootNode3(rootNode2);
            hasUpdate = false;//更新已处理
            //Log.d(TAG, "updateRootNode3 耗时：" + (System.currentTimeMillis() - t3) + ",总数=" + accessNodeMap.size());
        }
    }

    private static void reSetRootNode3(AccessibilityNodeInfo rootNode) {
        if (rootNode != null) {
//            int hashCode;
//            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
//                // 使用Objects.hash以增强哈希值的唯一性
//                hashCode = Objects.hash(rootNode);
//            } else {
//                hashCode = rootNode.hashCode();
//            }
//            accessNodeMap.put(hashCode, rootNode);
//            if (rootNode.getChildCount() > 0) {
//                for (int i = 0; i < rootNode.getChildCount(); i++) {
//                    reSetRootNode3(rootNode.getChild(i));
//                }
//            }
//            lastUpdateRootNodeTime = System.currentTimeMillis();

            //accessNodeMap.clear();
            Deque<AccessibilityNodeInfo> stack = new ArrayDeque<>();
            stack.push(rootNode);
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
                while (!stack.isEmpty()) {
                    AccessibilityNodeInfo currentNode = stack.pop();
                    // 使用Objects.hash以增强哈希值的唯一性
                    int hashCode2 = Objects.hash(currentNode);
                    //accessNodeMap.put(hashCode2, currentNode);
                    // 将子节点按逆序压入栈中，保证遍历顺序与递归相同（深度优先）
                    for (int i = currentNode.getChildCount() - 1; i >= 0; i--) {
                        AccessibilityNodeInfo child = currentNode.getChild(i);
                        if (child != null) {
                            stack.push(child);
                        }
                    }
                }
            } else {
                while (!stack.isEmpty()) {
                    AccessibilityNodeInfo currentNode = stack.pop();
                    int hashCode2= currentNode.hashCode();
                    //accessNodeMap.put(hashCode2, currentNode);
                    // 将子节点按逆序压入栈中，保证遍历顺序与递归相同（深度优先）
                    for (int i = currentNode.getChildCount() - 1; i >= 0; i--) {
                        AccessibilityNodeInfo child = currentNode.getChild(i);
                        if (child != null) {
                            stack.push(child);
                        }
                    }
                }
            }

            lastUpdateRootNodeTime = System.currentTimeMillis();
        }
    }

    private void reSetRootNode2(AccessibilityNodeInfo rootNode) {
        if (rootNode != null) {
            // 创建一个队列，用于存储待遍历的节点
            Queue<AccessibilityNodeInfo> queue = new LinkedList<>();
            queue.offer(rootNode);
            // 循环遍历队列中的节点
            while (!queue.isEmpty()) {
                // 从队列中取出一个节点
                AccessibilityNodeInfo currentNode = queue.poll();
                if (currentNode != null) {
                    // 处理当前节点的逻辑，例如打印节点的信息等
                    int hashCode;
                    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
                        // 使用Objects.hash以增强哈希值的唯一性
                        hashCode = Objects.hash(currentNode);
                    } else {
                        hashCode = currentNode.hashCode();
                    }
                    //accessNodeMap.put(hashCode, currentNode);

//                    //处理ID
//                    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR2) {
//                        String idStr = currentNode.getViewIdResourceName();
//                        if (!TextUtils.isEmpty(idStr)) {
//                            List<Integer> map = idMap.get(idStr);
//                            if (map == null) {
//                                map = new ArrayList<>();
//                            }
//                            map.add(hashCode);
//                            idMap.put(idStr, map);
//                        }
//                    }
//
//                    //处理Text
//                    String textStr = currentNode.getText() + "";
//                    if (currentNode.getText() != null && !TextUtils.isEmpty(textStr)) {
//                        List<Integer> textChildMap = textMap.get(textStr);
//                        if (textChildMap == null) {
//                            textChildMap = new ArrayList<>();
//                        }
//                        textChildMap.add(hashCode);
//                        textMap.put(textStr, textChildMap);
//                    }
//
//                    //处理描述
//                    String descriptionStr = currentNode.getContentDescription() + "";
//                    if (currentNode.getContentDescription() != null && !TextUtils.isEmpty(descriptionStr)) {
//                        List<Integer> descriptionChildMap = descriptionMap.get(descriptionStr);
//                        if (descriptionChildMap == null) {
//                            descriptionChildMap = new ArrayList<>();
//                        }
//                        descriptionChildMap.add(hashCode);
//                        descriptionMap.put(descriptionStr, descriptionChildMap);
//                    }

                    int count = currentNode.getChildCount();
                    // 将当前节点的所有子节点添加到队列中
                    for (int i = 0; i < count; i++) {
                        AccessibilityNodeInfo childNode = currentNode.getChild(i);
                        queue.offer(childNode);
                    }
                }
            }
            lastUpdateRootNodeTime = System.currentTimeMillis();
        }
    }
//
//    public static AccessibilityNodeInfo findOneFromParentByTextEquals(AccessibilityNodeInfo
//                                                                              pNode, String text) {
//        if (QuickAccessibilityService.instance != null && QuickAccessibilityService.instance.getRootInActiveWindow() != null && !TextUtils.isEmpty(text) && (pNode != null)) {
//            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
//                String str = text;
//                if (!str.startsWith("^")) {
//                    str = "^" + str;
//                }
//                if (!str.endsWith("$")) {
//                    str = str + "$";
//                }
//                List<AccessibilityNodeInfo> list2 = pNode.findAccessibilityNodeInfosByText(str);
//                if (list2.size() > 0) {
//                    return list2.get(0);
//                }
//            }
//            //如果查不到 则使用自定义遍历查询
//            AccessibilityNodeInfo nodeInfo = findOneFromParentByTextEquals2(pNode, text);
//            if (nodeInfo != null) {
//                return nodeInfo;
//            }
//        }
//        return null;
//    }

    /**
     * 匹配文字等于
     *
     * @param pNode
     * @param text
     * @return
     */
//    private static AccessibilityNodeInfo findOneFromParentByTextEquals2(AccessibilityNodeInfo
//                                                                                pNode, String text) {
//        if (!TextUtils.isEmpty(text) && (pNode != null)) {
//            //判断是否在当前屏幕
//            Rect rect1 = new Rect(0, 0, DisplayUtil.getScreenWidth(QuickAccessibilityService.instance.getApplicationContext()), DisplayUtil.getScreenHeight(QuickAccessibilityService.instance.getApplicationContext()));
//            Rect rect2 = QuickAccessibilityHelper.getBundsInScreen(pNode);
//            if (rect2 != null && rect1.intersect(rect2)) {
//                //如果查不到 则使用自定义遍历查询
//                if (!TextUtils.isEmpty(pNode.getText()) && pNode.getText().equals(text)) {
//                    return pNode;
//                }
//                int count = pNode.getChildCount();
//                for (int i = count - 1; i >= 0; i--) {
//                    AccessibilityNodeInfo nodeInfo = findOneFromParentByTextEquals(pNode.getChild(i), text);
//                    if (nodeInfo != null) {
//                        return nodeInfo;
//                    }
//                }
//            }
//        }
//        return null;
//    }


    public static List<AccessibilityNodeInfo> findOneByBuilder(FindBuilder findBuilder) {
        if (findBuilder != null && QuickAccessibilityService.instance != null) {
            AccessibilityNodeInfo rootAccessNodeInfo = QuickAccessibilityService.instance.getRootInActiveWindow();
            if (rootAccessNodeInfo != null) {
                if (!TextUtils.isEmpty(findBuilder.id)) {//id使用精准匹配
                    List<AccessibilityNodeInfo> accessibilityNodeInfoList;
                    if (findBuilder.anchorNodeInfo != null) {
                        accessibilityNodeInfoList = findBuilder.anchorNodeInfo.findAccessibilityNodeInfosByViewId(findBuilder.id);
                    } else {
                        accessibilityNodeInfoList = rootAccessNodeInfo.findAccessibilityNodeInfosByViewId(findBuilder.id);
                    }
                    //Log.i("accessibilityNodeInfoList","accessibilityNodeInfoList.size="+accessibilityNodeInfoList.size());
                    if (accessibilityNodeInfoList != null && accessibilityNodeInfoList.size() > 0) {
                        //Log.i("accessibilityNodeInfoList","findBuilder.id="+findBuilder.id+"---"+findBuilder.text_regex);
                        //Log.i("accessibilityNodeInfoList",""+accessibilityNodeInfoList.get(0).getText()+",id="+accessibilityNodeInfoList.get(0).getViewIdResourceName());
                        List<AccessibilityNodeInfo> list = new ArrayList<>();
                        W:
                        for (AccessibilityNodeInfo nodeInfo : accessibilityNodeInfoList) {
                            //Log.i("visible","visible="+findBuilder.visible );
                            //过滤显示状态
                            if (findBuilder.visible != -1) {
                                if ((nodeInfo.isVisibleToUser() ? 1 : 0) != findBuilder.visible) {
                                    //显示状态不匹配
                                    continue W;
                                }
                            }
                            //Log.i("clickable","clickable="+findBuilder.clickable );
                            //过滤点击状态
                            if (findBuilder.clickable != -1) {
                                if ((nodeInfo.isClickable() ? 1 : 0) != findBuilder.clickable) {
                                    //点击状态不匹配
                                    continue W;
                                }
                            }

                            //Log.i("viewClassName","viewClassName="+findBuilder.viewClassName );
                            //过滤类型
                            if (!TextUtils.isEmpty(findBuilder.viewClassName)) {
                                if (!findBuilder.viewClassName.equals(nodeInfo.getClassName())) {
                                    //控件类型不匹配
                                    continue W;
                                }
                            }
                            //Log.i("id","id="+findBuilder.id );
                            //过滤资源id
                            if (!TextUtils.isEmpty(findBuilder.id)) {
                                if (!findBuilder.id.equals(nodeInfo.getViewIdResourceName())) {
                                    continue W;
                                }
                            }
                            if (!TextUtils.isEmpty(findBuilder.text_regex)) {
                                if(TextUtils.isEmpty(nodeInfo.getText())){
                                    continue W;
                                }
                                Pattern pattern = Pattern.compile(findBuilder.text_regex);
                                Matcher matcher = pattern.matcher( nodeInfo.getText()+ "");
                                if (!matcher.find()) {
                                    continue W;
                                }
                            }
                            if (!TextUtils.isEmpty(findBuilder.text_equals)) {
                                if(TextUtils.isEmpty(nodeInfo.getText())){
                                    continue W;
                                }
                                if (!findBuilder.text_equals.equals(nodeInfo.getText())) {
                                    continue W;
                                }
                            }
                            if (!TextUtils.isEmpty(findBuilder.contentDescription)) {
                                if(TextUtils.isEmpty(nodeInfo.getContentDescription())){
                                    continue W;
                                }
                                if (!findBuilder.contentDescription.equals(nodeInfo.getContentDescription())) {
                                    continue W;
                                }
                            }
                            list.add(nodeInfo);
                            if (!findBuilder.isList) {
                                return list;
                            }
                        }

                        return list;
                    }
                    return null;
                }

                //处理搜索区域 根据条件中的findBuilder.fromNodeInfo查找子类
                List<AccessibilityNodeInfo> nodeInfoList = null;
                if (findBuilder.anchorNodeInfo != null) {
                    if (findBuilder.matchingInSub) {//匹配子节点
                        nodeInfoList = getAllChildNode(new ArrayList<>(), findBuilder.anchorNodeInfo);// covertToMap(findBuilder.anchorNodeInfo);
                    } else {//匹配父节点
                        nodeInfoList = getAllChildNode(new ArrayList<>(), findBuilder.anchorNodeInfo.getParent());// covertToMap(findBuilder.anchorNodeInfo.getParent());
                    }
                } else {
                    nodeInfoList = AccessNodeFinder.getInstance().getAccessNodeList();
                    //currentNodeInfoMap = AccessNodeFinder.getInstance().getAccessNodeMap();
                }
                W:
                for (AccessibilityNodeInfo nodeInfo : nodeInfoList) {
                    //for (Map.Entry entry : currentNodeInfoMap.entrySet()) {
                    //AccessibilityNodeInfo nodeInfo = (AccessibilityNodeInfo) entry.getValue();
                    if (!TextUtils.isEmpty(findBuilder.text_equals) || !TextUtils.isEmpty(findBuilder.text_regex)) {
                        if (TextUtils.isEmpty(nodeInfo.getText())) {
                            //文字为空不匹配
                            continue W;
                        }
                    }
                    //过滤显示状态
                    if (findBuilder.visible != -1) {
                        if ((nodeInfo.isVisibleToUser() ? 1 : 0) != findBuilder.visible) {
                            //显示状态不匹配
                            continue W;
                        }
                    }
                    //过滤点击状态
                    if (findBuilder.clickable != -1) {
                        if ((nodeInfo.isClickable() ? 1 : 0) != findBuilder.clickable) {
                            //点击状态不匹配
                            continue W;
                        }
                    }
                    //过滤描述
                    if (!TextUtils.isEmpty(findBuilder.contentDescription)) {
                        if (TextUtils.isEmpty(nodeInfo.getContentDescription())) {
                            continue W;
                        }
                        Pattern pattern = Pattern.compile(findBuilder.contentDescription);
                        Matcher matcher = pattern.matcher(nodeInfo.getContentDescription());
                        if (!matcher.find()) {
                            //描述不匹配
                            continue W;
                        }
                    }
                    //过滤类型
                    if (!TextUtils.isEmpty(findBuilder.viewClassName)) {
                        if (!findBuilder.viewClassName.equals(nodeInfo.getClassName())) {
                            //控件类型不匹配
                            continue W;
                        }
                    }
                    //过滤资源id
                    if (!TextUtils.isEmpty(findBuilder.id)) {
                        if (!findBuilder.id.equals(nodeInfo.getViewIdResourceName())) {
                            continue W;
                        }
                    }
                    if (!TextUtils.isEmpty(findBuilder.text_regex)) {
                        if (TextUtils.isEmpty(nodeInfo.getText())) {
                            //内容不匹配
                            continue W;
                        }
                        Pattern pattern = Pattern.compile(findBuilder.text_regex);
                        Matcher matcher = pattern.matcher(nodeInfo.getText());
                        if (!matcher.find()) {
                            //描述不匹配
                            continue W;
                        }
                    }
                    if (!TextUtils.isEmpty(findBuilder.text_equals)) {
                        if (TextUtils.isEmpty(nodeInfo.getText())) {
                            //内容不匹配
                            continue W;
                        }
                        if (!findBuilder.text_equals.equals(nodeInfo.getText() == null ? null : nodeInfo.getText().toString())) {
                            continue W;
                        }
                    }

                    List<AccessibilityNodeInfo> list = new ArrayList<>();
                    list.add(nodeInfo);
                    return list;
                }
            }
        }
//        if (!findBuilder.matchingInSub && findBuilder.anchorNodeInfo != null && findBuilder.anchorNodeInfo.getParent() != null) {
//            findBuilder.setAnchorNodeInfo(findBuilder.anchorNodeInfo.getParent());
//            return findOneByBuilder(findBuilder);
//        }
        return null;
    }

    /*private static Map<Integer, AccessibilityNodeInfo> covertToMap(AccessibilityNodeInfo fromNodeInfo) {
        Map<Integer, AccessibilityNodeInfo> nodeInfoMap = new LinkedHashMap<>();
        if (fromNodeInfo != null) {
            List<AccessibilityNodeInfo> accessibilityNodeInfoList = getAllChildNode(new ArrayList<>(), fromNodeInfo);
            // 处理当前节点的逻辑，例如打印节点的信息等
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
                for (AccessibilityNodeInfo nodeInfo : accessibilityNodeInfoList) {
                    // 使用Objects.hash以增强哈希值的唯一性
                    int hashCode = Objects.hash(nodeInfo);
                    nodeInfoMap.put(hashCode, nodeInfo);
                }
            } else {
                for (AccessibilityNodeInfo nodeInfo : accessibilityNodeInfoList) {
                    // 使用Objects.hash以增强哈希值的唯一性
                    int hashCode = nodeInfo.hashCode();
                    nodeInfoMap.put(hashCode, nodeInfo);
                }
            }
        }
        return nodeInfoMap;
    }*/

    /**
     * 从节点中读取所有子节点放到listz
     *
     * @param nodeInfos
     * @param fromNodeInfo
     * @return
     */
    private static List<AccessibilityNodeInfo> getAllChildNode(ArrayList<AccessibilityNodeInfo> nodeInfos, AccessibilityNodeInfo fromNodeInfo) {
        if (fromNodeInfo != null) {
            nodeInfos.add(fromNodeInfo);
            int count = fromNodeInfo.getChildCount();
            if (count> 0) {
                for (int i = 0; i < count; i++) {
                    getAllChildNode(nodeInfos, fromNodeInfo.getChild(i));
                }
            }
        }
        return nodeInfos;
    }

    private static List<AccessibilityNodeInfo> getAllChildNode2( AccessibilityNodeInfo fromNodeInfo) {
        ArrayList<AccessibilityNodeInfo> nodeInfos =new ArrayList<>();
        if (fromNodeInfo != null) {
//            nodeInfos.add(fromNodeInfo);
//            int count = fromNodeInfo.getChildCount();
//            if (count> 0) {
//                for (int i = 0; i < count; i++) {
//                    getAllChildNode(nodeInfos, fromNodeInfo.getChild(i));
//                }
//            }

            Deque<AccessibilityNodeInfo> stack = new ArrayDeque<>();
            stack.push(fromNodeInfo);
            while (!stack.isEmpty()) {
                AccessibilityNodeInfo currentNode = stack.pop();
                nodeInfos.add(currentNode);
                // 执行操作...

                // 将子节点按逆序压入栈中，保证遍历顺序与递归相同（深度优先）
                for (int i = currentNode.getChildCount() - 1; i >= 0; i--) {
                    AccessibilityNodeInfo child = currentNode.getChild(i);
                    if (child != null) {
                        stack.push(child);
                    }
                }
            }
        }
        return nodeInfos;
    }

    public AccessibilityNodeInfo findOneById(String str) {
        return AccessNodeFinder.FindBuilder.get().setId(str).findOne();
    }

    public static class FindBuilder {
        int clickable = -1;//0不可点击，1可点击
        int visible = -1;//0不可见，1可见
        AccessibilityNodeInfo anchorNodeInfo;//依赖参考锚点
        boolean matchingInSub;// true 匹配子节点，false 向父节点匹配
        //AccessibilityNodeInfo uperNodeInfo;//查找这个节点上层的节点
        String text_regex;
        String text_equals;
        String contentDescription;
        String id;
        String id_equals;
        String viewClassName;
        boolean isList = false;
        int resultCount = 1;//1findone 2findlist

        public static FindBuilder get() {
            return new FindBuilder();
        }

        public FindBuilder setResultCount(int resultCount) {
            this.resultCount = resultCount;
            return this;
        }

        /**
         * @param clickable 0不可点击，1可点击 -1不过滤
         * @return
         */
        public FindBuilder setClickable(int clickable) {
            this.clickable = clickable;
            return this;
        }

        /**
         * @param visible 0不可见，1可见 -1不过滤
         * @return
         */
        public FindBuilder setVisible(int visible) {
            this.visible = visible;
            return this;
        }

        public FindBuilder setViewClassName(String viewClassName) {
            this.viewClassName = viewClassName;
            return this;
        }

        public FindBuilder setId(String id) {
            this.id = id;
            return this;
        }

        public FindBuilder setId_equals(String id_equals) {
            this.id_equals = id_equals;
            return this;
        }

        public FindBuilder setText_equals(String text_equals) {
            this.text_equals = text_equals;
            return this;
        }

        public FindBuilder setText_regex(String text_regex) {
            this.text_regex = text_regex;
            return this;
        }

        public FindBuilder setAnchorNodeInfo(AccessibilityNodeInfo anchorNodeInfo) {
            this.anchorNodeInfo = anchorNodeInfo;
            return this;
        }

        public FindBuilder setAnchorNodeInfo(AccessibilityNodeInfo anchorNodeInfo, int level) {
            AccessibilityNodeInfo nodeInfo = anchorNodeInfo;
            for (int i = 0; i < Math.abs(level); i++) {
                nodeInfo = nodeInfo.getParent();
            }
            this.anchorNodeInfo = nodeInfo;
            return this;
        }

//        public FindBuilder setMatchingInSub(boolean matchingInSub) {
//            this.matchingInSub = matchingInSub;
//            return this;
//        }

        public FindBuilder setContentDescription(String contentDescription) {
            this.contentDescription = contentDescription;
            return this;
        }

        public AccessibilityNodeInfo findOne() {
            isList = false;
            long t1 = System.currentTimeMillis();
            List<AccessibilityNodeInfo> list = findOneByBuilder(this);
            if (list != null && list.size() > 0) {
                Log.d(TAG, "查询耗时：" + (System.currentTimeMillis() - t1));
                return list.get(0);
            }
            return null;
        }

        public List<AccessibilityNodeInfo> findList() {
            isList = true;
            return findOneByBuilder(this);
        }
    }

}
